import sys
# add directory in which script is located to python path
script_dir = "/".join(__file__.split("/")[:-1])
catalogs_dir = script_dir + "/catalogs"
if script_dir == "":
    script_dir = "."
if script_dir not in sys.path:
    sys.path.append(script_dir)
if catalogs_dir not in sys.path:
        sys.path.append(catalogs_dir)
import re, urllib, traceback
from collections import defaultdict
from django.utils import simplejson
from lxml import etree
import millenium
reload(millenium)
#import catalogs.millenium as catalog_millenium 


pathinfoformat = re.compile('/([^/]*)/([^/]*)/([^/]*)/(.*)')

pluginFactory = {
        'millenium' : millenium.handler
}

# Returns the path to the config file for a given edition
#
def getConfigFilePath(edition):
        re1='.*?'       # Non-greedy match on filler
        #re2='((?:[a-z][a-z]*[0-9]+[a-z0-9]*))'  # Alphanum 1
        #re2='((?:[a-zA-Z0-9][a-zA-Z0-9._]+))'
        #re2='((?:[0-9][a-z0-9_]*))'
        re2='^[0-9A-Fa-f]{8}(\\.\\d+)?$'
        #re2='\\d+' 
        path = 'http://libx.org/editions/'
        rg = re.compile(re2)
        m = rg.search(edition)
        if m:
            path += edition[:2] 
            path += '/'
            path += edition[2:4]
            path += '/'
        path += edition
        path += '/config.xml'
        return path

def getCatalogConfig(xmlDoc,catalog,sterm):
        try:
                i = int(catalog)
        except ValueError:
                i = -1 
                return 'the index of ' + catalog + ' is not a integer, please use a valid integer'
        val = xmlDoc.xpath('/edition/catalogs/*[' + str(i + 1) + ']')
        try:
            val = val[0]
        except IndexError:
            return 'the catalog index of ' + catalog + ' is not valid. please use a valid catalog index'
        tag = val.tag
        attributes = val.attrib 
        length = len(attributes.keys()) 
        dict = {}
        for item in attributes:
                dict[item] = attributes.get(item) 

        xisbn = val.xpath('xisbn')[0].attrib
        for item in xisbn:
                dict[item] = xisbn.get(item)

        #dispatch to the correct plugin
        #return catalogs_dir
        if pluginFactory.has_key(tag):
                func = pluginFactory[tag]
                return func(dict, sterm)
        else:
                return 'the catalog ' + tag + ' is not supported'


def notfound(env, start_response):
    body = "Not Found, env = \n" \
       + ''.join(sorted([k + " -> " + str(v) + "\n" for k, v in env.items()]))

    params = dict([(urllib.unquote_plus(k), urllib.unquote_plus(v))
        for k, v in [kv.strip().split('=', 1) \
                     for kv in env['QUERY_STRING'].split('&') if '=' in kv]])

    body = body + "\nparams:\n" \
       + ''.join(sorted([k + " -> " + str(v) + "\n" for k, v in params.items()]))
    headers = [('Content-Type', 'text/plain'), \
               ('Cache-Control', 'max-age=1,must-revalidate')]
    start_response("404 Not Found", headers)
    return [body]


#
# Callable 'application' is the WSGI entry point
#
def application(env, start_response):
        params = dict([(urllib.unquote_plus(k), urllib.unquote_plus(v))
        for k, v in [kv.strip().split('=', 1) \
                     for kv in env['QUERY_STRING'].split('&') if '=' in kv]])

        m = pathinfoformat.match(env['PATH_INFO'])
        (edition, catalog, keyword, search) = m.groups()
        
        configFilePath = getConfigFilePath(edition)
        #try:
        xmlDoc = etree.parse(configFilePath)
        #except IOError:
        #    headers = [('Content-Type', 'text/plain'), \
        #        ('Cache-Control', 'max-age=1,must-revalidate')]
        #    start_response("404 Not Found", headers)
        #    return ['Please use a valid edition and catalog index']

        #converter = OpacJSON(etree.parse(configFilePath))
        prefix = {
                'oclc' : 'o',
                'title' : 't',
                'isbn' : 'i',
                'bibrecord' : '.b'
        }
        
        if prefix.has_key(keyword):
                results = getCatalogConfig(xmlDoc, catalog, prefix[keyword] + search)
                body = simplejson.dumps(results)
                if params.has_key('jsoncallback'):
                    body = params.get('jsoncallback') + "(" + body + ")"
                if params.has_key('callback'):
                    body = params.get('callback') + "(" + body + ")"

                headers = [('Content-Type', 'application/javascript;charset=utf-8'), \
                   ('Cache-Control', 'max-age=1,must-revalidate')]
                start_response("200 OK", headers)
                return [body]
#       return notfound(env, start_response)    

if __name__ == '__main__':
    print 'main' 
